'show-chrome': {},
'size-changed': {},
},
-}, class WindowPreview extends St.Widget {
+}, class WindowPreview extends Shell.WindowPreview {
_init(metaWindow, workspace, overviewAdjustment) {
this.metaWindow = metaWindow;
this.metaWindow._delegate = this;
offscreen_redirect: Clutter.OffscreenRedirect.AUTOMATIC_FOR_OPACITY,
});
- this._windowContainer = new Clutter.Actor({
+ const windowContainer = new Clutter.Actor({
pivot_point: new Graphene.Point({ x: 0.5, y: 0.5 }),
});
- this._windowContainer.connect('notify::scale-x',
+ this.window_container = windowContainer;
+
+ windowContainer.connect('notify::scale-x',
() => this._adjustOverlayOffsets());
// gjs currently can't handle setting an actors layout manager during
// the initialization of the actor if that layout manager keeps track
// of its container, so set the layout manager after creating the
// container
- this._windowContainer.layout_manager = new Shell.WindowPreviewLayout();
- this.add_child(this._windowContainer);
+ windowContainer.layout_manager = new Shell.WindowPreviewLayout();
+ this.add_child(windowContainer);
this._addWindow(metaWindow);
this._stackAbove = null;
this._cachedBoundingBox = {
- x: this._windowContainer.layout_manager.bounding_box.x1,
- y: this._windowContainer.layout_manager.bounding_box.y1,
- width: this._windowContainer.layout_manager.bounding_box.get_width(),
- height: this._windowContainer.layout_manager.bounding_box.get_height(),
+ x: windowContainer.layout_manager.bounding_box.x1,
+ y: windowContainer.layout_manager.bounding_box.y1,
+ width: windowContainer.layout_manager.bounding_box.get_width(),
+ height: windowContainer.layout_manager.bounding_box.get_height(),
};
- this._windowContainer.layout_manager.connect(
+ windowContainer.layout_manager.connect(
'notify::bounding-box', layout => {
this._cachedBoundingBox = {
x: layout.bounding_box.x1,
pivot_point: new Graphene.Point({ x: 0.5, y: 0.5 }),
});
this._icon.add_constraint(new Clutter.BindConstraint({
- source: this._windowContainer,
+ source: windowContainer,
coordinate: Clutter.BindCoordinate.POSITION,
}));
this._icon.add_constraint(new Clutter.AlignConstraint({
- source: this._windowContainer,
+ source: windowContainer,
align_axis: Clutter.AlignAxis.X_AXIS,
factor: 0.5,
}));
this._icon.add_constraint(new Clutter.AlignConstraint({
- source: this._windowContainer,
+ source: windowContainer,
align_axis: Clutter.AlignAxis.Y_AXIS,
pivot_point: new Graphene.Point({ x: -1, y: ICON_OVERLAP }),
factor: 1,
reactive: true,
});
this._title.add_constraint(new Clutter.BindConstraint({
- source: this._windowContainer,
+ source: windowContainer,
coordinate: Clutter.BindCoordinate.X,
}));
const iconBottomOverlap = ICON_SIZE * (1 - ICON_OVERLAP);
this._title.add_constraint(new Clutter.BindConstraint({
- source: this._windowContainer,
+ source: windowContainer,
coordinate: Clutter.BindCoordinate.Y,
offset: scaleFactor * (iconBottomOverlap + ICON_TITLE_SPACING),
}));
this._title.add_constraint(new Clutter.AlignConstraint({
- source: this._windowContainer,
+ source: windowContainer,
align_axis: Clutter.AlignAxis.X_AXIS,
factor: 0.5,
}));
this._title.add_constraint(new Clutter.AlignConstraint({
- source: this._windowContainer,
+ source: windowContainer,
align_axis: Clutter.AlignAxis.Y_AXIS,
pivot_point: new Graphene.Point({ x: -1, y: 0 }),
factor: 1,
child: new St.Icon({ icon_name: 'preview-close-symbolic' }),
});
this._closeButton.add_constraint(new Clutter.BindConstraint({
- source: this._windowContainer,
+ source: windowContainer,
coordinate: Clutter.BindCoordinate.POSITION,
}));
this._closeButton.add_constraint(new Clutter.AlignConstraint({
- source: this._windowContainer,
+ source: windowContainer,
align_axis: Clutter.AlignAxis.X_AXIS,
pivot_point: new Graphene.Point({ x: 0.5, y: -1 }),
factor: this._closeButtonSide === St.Side.LEFT ? 0 : 1,
}));
this._closeButton.add_constraint(new Clutter.AlignConstraint({
- source: this._windowContainer,
+ source: windowContainer,
align_axis: Clutter.AlignAxis.Y_AXIS,
pivot_point: new Graphene.Point({ x: -1, y: 0.5 }),
factor: 0,
});
}
- vfunc_get_preferred_width(forHeight) {
- const themeNode = this.get_theme_node();
-
- // Only include window previews in size request, not chrome
- const [minWidth, natWidth] =
- this._windowContainer.get_preferred_width(
- themeNode.adjust_for_height(forHeight));
-
- return themeNode.adjust_preferred_width(minWidth, natWidth);
- }
-
- vfunc_get_preferred_height(forWidth) {
- const themeNode = this.get_theme_node();
- const [minHeight, natHeight] =
- this._windowContainer.get_preferred_height(
- themeNode.adjust_for_width(forWidth));
-
- return themeNode.adjust_preferred_height(minHeight, natHeight);
- }
-
- vfunc_allocate(box) {
- this.set_allocation(box);
-
- for (const child of this)
- child.allocate_available_size(0, 0, box.get_width(), box.get_height());
- }
-
_updateIconScale() {
const { ControlsState } = OverviewControls;
const { currentState, initialState, finalState } =
});
});
- const [width, height] = this._windowContainer.get_size();
+ const [width, height] = this.window_container.get_size();
const { scaleFactor } = St.ThemeContext.get_for_stage(global.stage);
const activeExtraSize = WINDOW_ACTIVE_SIZE_INC * 2 * scaleFactor;
const origSize = Math.max(width, height);
const scale = (origSize + activeExtraSize) / origSize;
- this._windowContainer.ease({
+ this.window_container.ease({
scale_x: scale,
scale_y: scale,
duration: animate ? WINDOW_SCALE_TIME : 0,
});
});
- this._windowContainer.ease({
+ this.window_container.ease({
scale_x: 1,
scale_y: 1,
duration: animate ? WINDOW_SCALE_TIME : 0,
// Assume that scale-x and scale-y update always set
// in lock-step; that allows us to not use separate
// handlers for horizontal and vertical offsets
- const previewScale = this._windowContainer.scale_x;
+ const previewScale = this.window_container.scale_x;
const [previewWidth, previewHeight] =
- this._windowContainer.allocation.get_size();
+ this.window_container.allocation.get_size();
const heightIncrease =
Math.floor(previewHeight * (previewScale - 1) / 2);
}
_addWindow(metaWindow) {
- const clone = this._windowContainer.layout_manager.add_window(metaWindow);
+ const clone = this.window_container.layout_manager.add_window(metaWindow);
if (!clone)
return;
}
_deleteAll() {
- const windows = this._windowContainer.layout_manager.get_windows();
+ const windows = this.window_container.layout_manager.get_windows();
// Delete all windows, starting from the bottom-most (most-modal) one
for (const window of windows.reverse())
}
_hasAttachedDialogs() {
- return this._windowContainer.layout_manager.get_windows().length > 1;
+ return this.window_container.layout_manager.get_windows().length > 1;
}
_updateAttachedDialogs() {
--- /dev/null
+#include "config.h"
+
+#include "shell-window-preview.h"
+
+enum
+{
+ PROP_0,
+
+ PROP_WINDOW_CONTAINER,
+
+ PROP_LAST
+};
+
+static GParamSpec *obj_props[PROP_LAST] = { NULL, };
+
+struct _ShellWindowPreview
+{
+ /*< private >*/
+ StWidget parent_instance;
+
+ ClutterActor *window_container;
+};
+
+G_DEFINE_TYPE (ShellWindowPreview, shell_window_preview, ST_TYPE_WIDGET);
+
+static void
+shell_window_preview_get_property (GObject *gobject,
+ unsigned int property_id,
+ GValue *value,
+ GParamSpec *pspec)
+{
+ ShellWindowPreview *self = SHELL_WINDOW_PREVIEW (gobject);
+
+ switch (property_id)
+ {
+ case PROP_WINDOW_CONTAINER:
+ g_value_set_object (value, self->window_container);
+ break;
+
+ default:
+ G_OBJECT_WARN_INVALID_PROPERTY_ID (gobject, property_id, pspec);
+ }
+}
+
+static void
+shell_window_preview_set_property (GObject *gobject,
+ unsigned int property_id,
+ const GValue *value,
+ GParamSpec *pspec)
+{
+ ShellWindowPreview *self = SHELL_WINDOW_PREVIEW (gobject);
+
+ switch (property_id)
+ {
+ case PROP_WINDOW_CONTAINER:
+ g_set_object (&self->window_container, g_value_get_object (value));
+ break;
+
+ default:
+ G_OBJECT_WARN_INVALID_PROPERTY_ID (gobject, property_id, pspec);
+ }
+}
+
+static void
+shell_window_preview_get_preferred_width (ClutterActor *actor,
+ float for_height,
+ float *min_width_p,
+ float *natural_width_p)
+{
+ ShellWindowPreview *self = SHELL_WINDOW_PREVIEW (actor);
+ StThemeNode *theme_node = st_widget_get_theme_node (ST_WIDGET (self));
+ float min_width, nat_width;
+
+ st_theme_node_adjust_for_height (theme_node, &for_height);
+
+ clutter_actor_get_preferred_width (self->window_container, for_height,
+ &min_width, &nat_width);
+
+ st_theme_node_adjust_preferred_width (theme_node, &min_width, &nat_width);
+
+ if (min_width_p)
+ *min_width_p = min_width;
+
+ if (natural_width_p)
+ *natural_width_p = nat_width;
+}
+
+static void
+shell_window_preview_get_preferred_height (ClutterActor *actor,
+ float for_width,
+ float *min_height_p,
+ float *natural_height_p)
+{
+ ShellWindowPreview *self = SHELL_WINDOW_PREVIEW (actor);
+ StThemeNode *theme_node = st_widget_get_theme_node (ST_WIDGET (self));
+ float min_height, nat_height;
+
+ st_theme_node_adjust_for_width (theme_node, &for_width);
+
+ clutter_actor_get_preferred_height (self->window_container, for_width,
+ &min_height, &nat_height);
+
+ st_theme_node_adjust_preferred_height (theme_node, &min_height, &nat_height);
+
+ if (min_height_p)
+ *min_height_p = min_height;
+
+ if (natural_height_p)
+ *natural_height_p = nat_height;
+}
+
+static void
+shell_window_preview_allocate (ClutterActor *actor,
+ const ClutterActorBox *box)
+{
+ StThemeNode *theme_node = st_widget_get_theme_node (ST_WIDGET (actor));
+ ClutterActorBox content_box;
+ float x, y, max_width, max_height;
+ ClutterActorIter iter;
+ ClutterActor *child;
+
+ clutter_actor_set_allocation (actor, box);
+
+ st_theme_node_get_content_box (theme_node, box, &content_box);
+
+ clutter_actor_box_get_origin (&content_box, &x, &y);
+ clutter_actor_box_get_size (&content_box, &max_width, &max_height);
+
+ clutter_actor_iter_init (&iter, actor);
+ while (clutter_actor_iter_next (&iter, &child))
+ clutter_actor_allocate_available_size (child, x, y, max_width, max_height);
+}
+
+static void
+shell_window_preview_dispose (GObject *gobject)
+{
+ ShellWindowPreview *self = SHELL_WINDOW_PREVIEW (gobject);
+
+ g_clear_object (&self->window_container);
+
+ G_OBJECT_CLASS (shell_window_preview_parent_class)->dispose (gobject);
+}
+
+static void
+shell_window_preview_init (ShellWindowPreview *self)
+{
+}
+
+static void
+shell_window_preview_class_init (ShellWindowPreviewClass *klass)
+{
+ ClutterActorClass *actor_class = CLUTTER_ACTOR_CLASS (klass);
+ GObjectClass *gobject_class = G_OBJECT_CLASS (klass);
+
+ actor_class->get_preferred_width = shell_window_preview_get_preferred_width;
+ actor_class->get_preferred_height = shell_window_preview_get_preferred_height;
+ actor_class->allocate = shell_window_preview_allocate;
+
+ gobject_class->dispose = shell_window_preview_dispose;
+ gobject_class->get_property = shell_window_preview_get_property;
+ gobject_class->set_property = shell_window_preview_set_property;
+
+ /**
+ * ShellWindowPreview:window-container:
+ */
+ obj_props[PROP_WINDOW_CONTAINER] =
+ g_param_spec_object ("window-container",
+ "window-container",
+ "window-container",
+ CLUTTER_TYPE_ACTOR,
+ G_PARAM_READWRITE |
+ G_PARAM_STATIC_STRINGS);
+
+ g_object_class_install_properties (gobject_class, PROP_LAST, obj_props);
+}